package com.micro.monitoring.network;

import android.annotation.SuppressLint;
import android.content.Context;
import android.util.Log;

import com.micro.monitoring.Constant;
import com.micro.monitoring.basic.BasicCallBack;
import com.micro.monitoring.basic.BasicSharePreferences;

import org.jetbrains.annotations.NotNull;
import org.json.JSONException;
import org.json.JSONObject;

import java.io.IOException;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.Objects;

import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;
import javax.net.ssl.TrustManager;
import javax.net.ssl.X509TrustManager;

import okhttp3.Call;
import okhttp3.Callback;
import okhttp3.MediaType;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.RequestBody;
import okhttp3.Response;

public class SendOkHttp {
    private Context context;
    private static SendOkHttp sendOkHttp;
    private OkHttpClient client;
    private BasicCallBack basicCallBack;

    public SendOkHttp() {
//        client = new OkHttpClient().newBuilder().hostnameVerifier(new HostnameVerifier() {
//            @SuppressLint("BadHostnameVerifier")
//            @Override
//            public boolean verify(String hostname, SSLSession session) {
//                //强行返回true 即验证成功
//                return true;
//            }
//        }).build();
        client = getUnsafeOkHttpClient();
    }

    public void init(Context context, BasicCallBack basicCallBack) {
        this.context = context;
        this.basicCallBack = basicCallBack;
    }

    @SuppressLint("CommitPrefEdits")

    public static SendOkHttp getInstance() {
        if (sendOkHttp == null) {
            synchronized (SendOkHttp.class) {
                if (sendOkHttp == null) {
                    sendOkHttp = new SendOkHttp();
                }
            }
        }
        return sendOkHttp;
    }


    //    public String sendRequest(String address, String data) {
//        try {
//            OkHttpClient client = new OkHttpClient().newBuilder().build();
//            MediaType mediaType = MediaType.Companion.parse("application/json;charset=utf-8");
//            RequestBody body = RequestBody.Companion.create(data, mediaType);
//            Request request = new Request.Builder()
//                    .url(address)
//                    .post(body)
//                    .header(Constant.TOKEN,sharedPreferences.getString(Constant.TOKEN,Constant.EMPTY_DATA))
//                    .build();
//            Response response = client.newCall(request).execute();
//            String responseData = response.body().string();
//            System.out.println(responseData + "kl");
//            return responseData;
//        } catch (IOException e) {
//            e.printStackTrace();
//        }
//        return null;
//    }
//
//    public void sendRequestVoidResponse(final String address, final String data) {
//        new Thread(new Runnable() {
//            @Override
//            public void run() {
//                try {
//                    OkHttpClient client = new OkHttpClient().newBuilder().build();
//                    MediaType mediaType = MediaType.Companion.parse("application/json;charset=utf-8");
//                    RequestBody body = RequestBody.Companion.create(data, mediaType);
//                    Request request = new Request.Builder()
//                            .url(address)
//                            .post(body)
//                            .build();
//                    Response response = client.newCall(request).execute();
//                    String responseData = response.body().string();
//                    System.out.println(responseData + "kk");
//                } catch (IOException e) {
//                    e.printStackTrace();
//                }
//            }
//        }).start();
//    }
    public void sendGet(String address, int id) {
        final Request request = new Request.Builder()
                .url(address)
                .header(Tag.TOKEN, BasicSharePreferences.getSharedPreferences(context).getString(Constant.TOKEN, Constant.EMPTY_DATA))
                .build();
        setCall(client.newCall(request), id);
    }

    public void sendDel(String address, int id) {
        final Request request = new Request.Builder()
                .url(address)
                .delete()
                .header(Tag.TOKEN, BasicSharePreferences.getSharedPreferences(context).getString(Constant.TOKEN, Constant.EMPTY_DATA))
                .build();
        setCall(client.newCall(request), id);
    }

    public void sendPost(String address, String data, int id) {
        MediaType mediaType = MediaType.Companion.parse("application/json;charset=utf-8");
        RequestBody body = RequestBody.Companion.create(data, mediaType);
        final Request request = new Request.Builder()
                .url(address)
                .post(body)
                .header(Tag.TOKEN, BasicSharePreferences.getSharedPreferences(context).getString(Constant.TOKEN, Constant.EMPTY_DATA))
                .build();
        setCall(client.newCall(request), id);
    }

    public void sendPut(String address, String data, int id) {
        MediaType mediaType = MediaType.Companion.parse("application/json;charset=utf-8");
        RequestBody body = RequestBody.Companion.create(data, mediaType);
        final Request request = new Request.Builder()
                .url(address)
                .put(body)
                .header(Tag.TOKEN, BasicSharePreferences.getSharedPreferences(context).getString(Constant.TOKEN, Constant.EMPTY_DATA))
                .build();
        setCall(client.newCall(request), id);
    }

    private void setCall(Call call, int id) {
        call.enqueue(new Callback() {
            @Override
            public void onFailure(@NotNull Call call, @NotNull IOException e) {
                basicCallBack.onError();
                basicCallBack.onComplete();
            }

            @Override
            public void onResponse(@NotNull Call call, @NotNull Response response) throws IOException {
                String data = Objects.requireNonNull(response.body()).string();
                Log.d(Constant.TAG, "onResponse: " + data);
                basicCallBack.onSuccess(data, id);
                basicCallBack.onComplete();
            }
        });
    }

    public void sendTokenRequest(String account, String password) {
        Log.d(Constant.TAG, "sendTokenRequest: ");
//        new Thread(new Runnable() {
//            @Override
//            public void run() {
        Log.d(Constant.TAG, "sendTokenRequest: " + client.sslSocketFactory());
        Log.d(Constant.TAG, "sendTokenRequest: " + client.hostnameVerifier());
        String address = Urls.BASE_URL_HTTPS + Urls.BASE_URL + Urls.TOKEN_ACCOUNT +
                account +
                Urls.TOKEN_PASSWORD +
                password;
        Log.d(Constant.TAG, "sendTokenRequest: " + address);
        final Request request = new Request.Builder()
                .url(address)
                .build();
        Call call = client.newCall(request);
        Log.d(Constant.TAG, "sendTokenRequest: " + call);
        call.enqueue(new Callback() {
            @Override
            public void onFailure(@NotNull Call call, @NotNull IOException e) {
                Log.d(Constant.TAG, "onFailure: " + e + call);
                basicCallBack.onFailure(Constant.EMPTY_DATA);
                basicCallBack.onComplete();
            }

            @Override
            public void onResponse(@NotNull Call call, @NotNull Response response) throws IOException {
                String data = Objects.requireNonNull(response.body()).string();
                Log.d(Constant.TAG, "onResponse: " + data);
                //       TokenBean tokenBean=gson.fromJson(data,TokenBean.class);
                //     Log.d(Constant.TAG, "onResponse: "+tokenBean.getCode());
                try {
//                    JSONArray jsonArray=new JSONArray(data)
                    JSONObject jsonObject = new JSONObject(data);
//                            String token = jsonObject.getString("data");
                    String message = jsonObject.getString(Constant.MESSAGE);
//                            LogUtils.d(message);
//                            Log.d(Constant.TAG, "onResponse: " + token);
                    BasicSharePreferences.getEditor(context).putString(Constant.TOKEN, jsonObject.getJSONObject(Constant.DATA).getString(Constant.TOKEN));
                    BasicSharePreferences.getEditor(context).putInt(Constant.USER_ID, jsonObject.getJSONObject(Constant.DATA).getInt(Constant.USER_ID));
                    BasicSharePreferences.getEditor(context).putString(Constant.MESSAGE, message);
                    BasicSharePreferences.getEditor(context).apply();
                    basicCallBack.onSuccess(message, Constant.CALL_ID_TOKEN);
                    basicCallBack.onComplete();
                } catch (JSONException e) {
                    e.printStackTrace();
                }
                //Log.d(Constant.TAG, "onResponse: " + response.body().string());
            }
        });
        Log.d(Constant.TAG, "sendOkHttp run: " + address);
//            }
//        }).start();
    }

    public static OkHttpClient getUnsafeOkHttpClient() {

        try {

            final TrustManager[] trustAllCerts = new TrustManager[]{

                    new X509TrustManager() {

                        @SuppressLint("TrustAllX509TrustManager")
                        @Override

                        public void checkClientTrusted(X509Certificate[] chain, String authType) {

                        }

                        @SuppressLint("TrustAllX509TrustManager")
                        @Override

                        public void checkServerTrusted(X509Certificate[] chain, String authType) {

                        }

                        @Override

                        public X509Certificate[] getAcceptedIssuers() {

                            return new X509Certificate[]{};

                        }

                    }};

            final SSLContext sslContext = SSLContext.getInstance("SSL");

            sslContext.init(null, trustAllCerts, new java.security.SecureRandom());

            final javax.net.ssl.SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory();

            OkHttpClient.Builder builder = new OkHttpClient.Builder();

            builder.sslSocketFactory(sslSocketFactory, new X509TrustManager() {
                @SuppressLint("TrustAllX509TrustManager")
                @Override
                public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {

                }

                @SuppressLint("TrustAllX509TrustManager")
                @Override
                public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {

                }

                @Override
                public X509Certificate[] getAcceptedIssuers() {
                    return new X509Certificate[0];
                }
            });

            builder.hostnameVerifier(new HostnameVerifier() {

                @SuppressLint("BadHostnameVerifier")
                @Override

                public boolean verify(String hostname, SSLSession session) {

                    return true;

                }

            });

            return builder.build();

        } catch (Exception e) {

            throw new RuntimeException(e);

        }

    }

}